﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.ComponentModel.DataAnnotations;
using System.ComponentModel;
using System.Linq.Expressions;

namespace SoGame.Model
{
    [Table("GamePlays")]
    public class GamePlay : INotifyPropertyChanged
    {
        private int id;
        private int? playerID;
        private DateTime date;
        private int score;
        private string game;
        private byte[] photo;

        public GamePlay() {
            this.Date = DateTime.Now;
        }


        /// <summary>
        /// Gets or sets the ID.
        /// </summary>
        /// <value>
        /// The ID.
        /// </value>
        [Key]
        [Column("ID")]
        public int ID {
            get { return this.id; }
            set {
                if (this.id != value) {
                    this.id = value;
                    this.OnPropertyChanged(() => ID);
                }
            }
        }

        /// <summary>
        /// Gets or sets the player ID.
        /// </summary>
        /// <value>
        /// The player ID.
        /// </value>
        [Column("PlayerID")]
        public int? PlayerID {
            get { return this.playerID; }
            set {
                if (this.playerID != value) {
                    this.playerID = value;
                    this.OnPropertyChanged(() => PlayerID);
                }
            }
        }

        /// <summary>
        /// Gets or sets the date.
        /// </summary>
        /// <value>
        /// The date.
        /// </value>
        [Column("Date")]
        public DateTime Date {
            get { return this.date; }
            set {
                if (this.date != value) {
                    this.date = value;
                    this.OnPropertyChanged(() => Date);
                }
            }
        }

        /// <summary>
        /// Gets or sets the photo.
        /// </summary>
        /// <value>
        /// The photo.
        /// </value>
        [Column("Photo")]
        public byte[] Photo
        {
            get
            {
                return this.photo;
            }
            set
            {
                if (this.photo != value)
                {
                    this.photo = value;
                    this.OnPropertyChanged(() => Photo);
                }
            }
        }

        /// <summary>
        /// Gets or sets the game.
        /// </summary>
        /// <value>
        /// The game.
        /// </value>
        [Required]
        [Column("Game")]
        public string Game
        {
            get
            {
                return this.game;
            }
            set
            {
                if (this.game != value)
                {
                    this.game = value;
                    this.OnPropertyChanged(() => Game);
                }
            }
        }

        /// <summary>
        /// Gets or sets the score.
        /// </summary>
        /// <value>
        /// The score.
        /// </value>
        [Required]
        [Column("Score")]
        public int Score
        {
            get
            {
                return this.score;
            }
            set
            {
                if (this.score != value)
                {
                    this.score = value;
                    this.OnPropertyChanged(() => Score);
                }
            }
        }

        #region INotifyPropertyChanged
        /// <summary>
        /// Called when [property changed].
        /// </summary>
        /// <typeparam name="T"></typeparam>
        /// <param name="action">The action.</param>
        protected void OnPropertyChanged<T>(Expression<Func<T>> action)
        {
            var propertyName = GetPropertyName(action);
            OnPropertyChanged(propertyName);
        }

        /// <summary>
        /// Called when [property changed].
        /// </summary>
        /// <param name="propertyName">Name of the property.</param>
        private void OnPropertyChanged(string propertyName)
        {
            PropertyChangedEventHandler handler = PropertyChanged;
            if (handler != null)
            {
                var e = new PropertyChangedEventArgs(propertyName);
                handler(this, e);
            }
        }


        /// <summary>
        /// Gets the name of the property.
        /// </summary>
        /// <typeparam name="T"></typeparam>
        /// <param name="action">The action.</param>
        /// <returns></returns>
        private static string GetPropertyName<T>(Expression<Func<T>> action)
        {
            var expression = (MemberExpression)action.Body;
            var propertyName = expression.Member.Name;
            return propertyName;
        }

        /// <summary>
        /// Occurs when a property value changes.
        /// </summary>
        public event PropertyChangedEventHandler PropertyChanged;
        #endregion

        /// <summary>
        /// Gets or sets the player.
        /// </summary>
        /// <value>
        /// The player.
        /// </value>
        public virtual Player Player { get; set; }

        /// <summary>
        /// Gets or sets the sent mail.
        /// </summary>
        /// <value>
        /// The sent mail.
        /// </value>
        public virtual SentMail SentMail { get; set; }
    }
}
